package database;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;

import javax.swing.JOptionPane;

import xml_parser.Component;

public class DataBase {
	
	private ArrayList<Fragment> fgtList;
	private Reading rf;
	private Writing wf;
	
	public DataBase(String file){
		fgtList=new ArrayList<Fragment>();
		rf=new Reading(file);
		wf=new Writing(file);
		rf.parseFile();
		fgtList.addAll(rf.getDB());
	}
	
	public void addFragment(Fragment fgt){
		fgtList.add(fgt);
	}
	
	public void deleteFragment(Fragment fgt){
		//System.out.println(fgt.toString());
		for(int i=0;i<fgtList.size();i++){
			if(fgtList.get(i).getName().equalsIgnoreCase(fgt.getName())){
				fgtList.remove(i);
				i=fgtList.size();
			}
		}
		
	}
	
	public ArrayList<Fragment> getFragments(){
		return fgtList;
	}
	
	public String toString(){
		String db= "BEGIN_DataBase \r\n---------------------------------------\r\n\n";
		for(int i=0;i<fgtList.size();i++){
			db=db+fgtList.get(i).toString()+"\n---------------------------------------\r\n";
		}
		db=db+"END_DataBase \n";
		return db;
	}
	
	public boolean addComponentInDatabase(String process, String fragmentName, String position, ArrayList<Component> componentsList) {
		Fragment fgt=new Fragment(fragmentName, process, position);
		//System.out.println("FGT : "+fragmentName+process+position);
		if(isNew(fgt)&& isPositionOk(fgt)){
			for (int i=0; i<componentsList.size();i++){
				if(componentsList.get(i).getType().equals("MMME")){
					fgt.addElement(componentsList.get(i).getName(), new ArrayList<Operation>());
				}
				if(componentsList.get(i).getType().equals("MMMR")){
					fgt.addRelationship(componentsList.get(i).getName(), new ArrayList<Operation>());
				}
			}
			wf.writeNewFragment(fgt);
			this.addFragment(fgt);
			return true;
		}
		else{
			return false;
		}
	}
	
	public void addOperation(Fragment f,String comp,Operation op){
		for(int i=0; i<fgtList.size();i++){
			if(f.getName().equals(fgtList.get(i).getName())&& 
					f.getProcess().equals(fgtList.get(i).getProcess())){
				wf.addOperation(f, comp, op);
				fgtList.get(i).addOperation(comp, op);
			}
		}
		
	}

	private boolean isNew(Fragment fgt){
		for(int i=0; i<fgtList.size();i++){
			if(fgt.getName().equalsIgnoreCase(fgtList.get(i).getName())&& 
					fgt.getProcess().equalsIgnoreCase(fgtList.get(i).getProcess()))
				return false;
		}
		return true;
	}
	
	private boolean isPositionOk(Fragment fgt){
		for(int i=0; i<fgtList.size();i++){
			if(fgt.getPosition().equalsIgnoreCase(fgtList.get(i).getPosition())&& 
					fgt.getProcess().equalsIgnoreCase(fgtList.get(i).getProcess()))
				return false;
		}
		return true;
	}
	
	public HashSet<String> getProcessNameList(){
		HashSet<String> processNames= new HashSet<String>();
		for(int i=0; i<fgtList.size();i++)
			if(!processNames.contains(fgtList.get(i).getProcess()))
				processNames.add(fgtList.get(i).getProcess());
		return processNames;
	}
	
	public HashMap<String,ArrayList<String>> getFragmentList(String process){
		HashMap<String,ArrayList<String>> fragments= new HashMap<String,ArrayList<String>>();
		for(int i=0; i<fgtList.size();i++)
			if(fgtList.get(i).getProcess().equalsIgnoreCase(process)){
				fragments.put(fgtList.get(i).getName(), fgtList.get(i).getComponentNames());
			}
		return fragments;
	}
	
	public ArrayList<String> getFragmentNameList(String process){
		ArrayList<String> fgts=new ArrayList<String>();
		for(int i=0; i<fgtList.size();i++)
			if(fgtList.get(i).getProcess().equalsIgnoreCase(process)){
				fgts.add(fgtList.get(i).getName());
			}
		return fgts;
	}
	
	public HashSet<String> getAllFragmentNameList(){
		HashSet<String> fragmentNames= new HashSet<String>();
		for(int i=0; i<fgtList.size();i++)
				if(!fragmentNames.contains(fgtList.get(i).getName()))
					fragmentNames.add(fgtList.get(i).getName());
		return fragmentNames;
	}
	
	
	public Fragment getFragment(String process, String fragmentName) {
		for(int i=0; i<fgtList.size();i++){
			if(fragmentName.equalsIgnoreCase(fgtList.get(i).getName())&& 
					process.equalsIgnoreCase(fgtList.get(i).getProcess())){
				return fgtList.get(i);
			}
		}
		return null;
	}
	

	public boolean containsFragment(String fragmentName){
		for(int i=0; i<fgtList.size();i++){
			if(fragmentName.equalsIgnoreCase(fgtList.get(i).getName())){
				return true;
			}
		}
		return false;
	}
	
	public boolean containsProcess(String ProcessName){
		for(int i=0; i<fgtList.size();i++){
			if(ProcessName.equalsIgnoreCase(fgtList.get(i).getProcess())){
				return true;
			}
		}
		return false;
	}
	
	
	public ArrayList<String> getComponents(String process){
		ArrayList<String> components=new ArrayList<String>();
		for(int i=0; i<fgtList.size();i++){
			if(fgtList.get(i).getProcess().equalsIgnoreCase(process)){
				for(int j=0;j<fgtList.get(i).getComponentNames().size();j++){
					String compName=fgtList.get(i).getComponentNames().get(j);
					if(!components.contains(compName))
						components.add(compName);
				}
			}
			
		}
		return components;
	}

	public void removeFragment( String processName,String fragmentName) {
		Fragment fgt=getFragment(processName, fragmentName);
		this.deleteFragment(fgt);
		wf.removeFragment(fgt);
	}
	
}
